from pathlib import Path

import jieba


def cat_sentence(context: str, cut_all: bool = False, max_length: int = 30) -> str:
    """
    对中文文本进行分词，连接后返回不超过指定长度的结果（避免截断完整词语）
    :param context: 需要处理的中文文本
    :param cut_all: jieba分词模式，False为精确模式（默认），True为全模式
    :param max_length: 最大字符长度限制，默认为30
    :return: 分词后用空格连接的字符串，总长度不超过max_length
    """
    # 验证max_length参数有效性
    if not isinstance(max_length, int) or max_length <= 0:
        raise ValueError("max_length必须是正整数")

    # 处理空输入
    if not context.strip():
        return ""

    # 分词（支持不同模式）
    words = jieba.lcut(context, cut_all=cut_all)
    if not words:
        return ""

    total_length = 0
    selected_words = []

    for i, word in enumerate(words):
        # 计算当前词加入后的长度（首词不加空格，其他词加1个空格）
        word_len = len(word)
        add_len = word_len if i == 0 else (word_len + 1)

        # 超过最大长度则停止选择
        if total_length + add_len > max_length:
            # 如果是第一个词且超过长度限制，截断该词
            if i == 0:
                selected_words.append(word[:max_length])
                total_length = max_length
            break

        selected_words.append(word)
        total_length += add_len

    return " ".join(selected_words)


def replace_underscore_and_dot(original_path: str or Path, new_str: str) -> str:
    """
    替换路径中最后一个下划线(_)和最后一个点(.)之间的内容

    :param original_path: 原始文件路径（可以是字符串或Path对象），如 "resources/bert/models/model_bert_20250902.pkl"
    :param new_str: 用于替换的新字符串，如 "v2_best"
    :return: 替换后的路径，如 "resources/bert/models/model_bert_v2_best.pkl"
    ValueError: 当路径中没有下划线(_)或点(.)时抛出
    """
    # 将Path对象转换为字符串
    if isinstance(original_path, Path):
        original_path = str(original_path)

    # 查找最后一个下划线(_)的位置
    last_underscore_idx = original_path.rfind('_')
    # 查找最后一个点(.)的位置
    last_dot_idx = original_path.rfind('.')

    # 校验路径格式是否合法
    if last_underscore_idx == -1:
        raise ValueError("路径中未找到下划线(_)，无法完成替换")
    if last_dot_idx == -1:
        raise ValueError("路径中未找到点(.)，无法完成替换")
    if last_underscore_idx >= last_dot_idx:
        raise ValueError("最后一个下划线(_)必须在最后一个点(.)之前")

    # 截取前缀（到最后一个_，包含_）和后缀（从.到结尾，包含.）
    prefix = original_path[:last_underscore_idx + 1]  # +1 保留最后一个_
    suffix = original_path[last_dot_idx:]

    # 拼接新路径
    return prefix + new_str + suffix

def _use_replace_underscore_and_dot():
    path_template = "resources/bert/models/model_bert_20250902.pkl"
    version_str = "v2_best"
    new_path = replace_underscore_and_dot(path_template, version_str)
    assert new_path == "resources/bert/models/model_bert_v2_best.pkl", "替换失败"

    # 含多个下划线的路径测试
    complex_path = "models/bert_v1_train_20250902_final.pkl"
    new_complex_path = replace_underscore_and_dot(complex_path, "v2_final")
    assert new_complex_path == "models/bert_v1_train_20250902_v2_final.pkl", "替换失败"

    print("所有测试通过！")


if __name__ == '__main__':
    _use_replace_underscore_and_dot()


